const BaseControl = require('./baseController')
const sendToWormhole = require('stream-wormhole')
const awaitWriteStream = require('await-stream-ready').write
const fs = require('fs')
const path = require('path')
const dayjs = require('dayjs')

class BaseMultiUploadFilesController extends BaseControl {
	// 上传
	async MultiUploadFiles(category = 'default') {
		const ctx = this.ctx
		const parts = ctx.multipart()
		let data = [] // 返回结果
		let params = {}
		let part
		// parts() 返回 promise 对象
		let flag = false
		while ((part = await parts()) != null) {
			// 获取参数
			if (part.length) {
				const field = part[0]
				const value = part[1]
				// 拼接参数
				params[field] = value
			} else {
				if (!part.filename) {
					// 这时是用户没有选择文件就点击了上传(part 是 file stream，但是 part.filename 为空)
					// 需要做出处理，例如给出错误提示消息
					return { flag: false, message: '文件名缺失' }
				}
				// part 是上传的文件流
				const uploadBasePath = this.app.config.uploadDir
				// 生成文件名
				const filename = `${Date.now()}${Number.parseInt(
					Math.random() * 1000
				)}${path.extname(part.filename).toLocaleLowerCase()}`
				// 生成文件目录
				const dirname = dayjs(Date.now()).format('YYYY/MM/DD')
				function mkdirsSync(dirname) {
					if (fs.existsSync(dirname)) {
						// 这里是检测文件目录是否已经存在
						return true
					} else {
						if (mkdirsSync(path.dirname(dirname))) {
							fs.mkdirSync(dirname)
							return true
						}
					}
				}
				if (!flag)
					flag = mkdirsSync(path.join(uploadBasePath, category, dirname))
				// 生成写入路径
				const target = path.join(uploadBasePath, category, dirname, filename)
				try {
					// 文件处理，上传到云存储等等
					// const { url } = await this.ctx.oss.put(part.filename, part)
					const writeStream = fs.createWriteStream(target)
					await awaitWriteStream(part.pipe(writeStream))
					data.push({
						url: path.join(
							this.app.config.baseUrl,
							'public/uploads',
							category,
							dirname,
							filename
						),
						fields: part.filename,
					})
				} catch (err) {
					// 必须将上传的文件流消费掉，要不然浏览器响应会卡死
					console.log(err)
					await sendToWormhole(part)
					return { flag: false, message: '文件上传失败' }
				}
			}
		}
		return { flag: true, data, params }
	}
}

module.exports = BaseMultiUploadFilesController
